﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Shapes;
using Microsoft.Phone.Controls;
using Microsoft.Devices.Sensors;

namespace Experiments.MichaelKappel.Net.Tilt
{
    public sealed partial class MainPage : PhoneApplicationPage, IDisposable
    {
        private Accelerometer Accelerometer = new Accelerometer();
        private Color White = Color.FromArgb(255, 255, 255, 255);
        private Color Black = Color.FromArgb(255, 0, 0, 0); 

        private Axis.AxisGraphInfo X
        {
            get;
            set;
        }

        private Axis.AxisGraphInfo Y
        {
            get;
            set;
        }

        private Axis.AxisGraphInfo Z
        {
            get;
            set;
        }

        private Axis.AxisGraphInfo CurrentAxis
        {
            get;
            set;
        }

        public MainPage()
        {  
            InitializeComponent();
            X = new Axis.AxisGraphInfo(Accelerometer, ppSymbolX);
            Y = new Axis.AxisGraphInfo(Accelerometer, ppSymbolY);
            Z = new Axis.AxisGraphInfo(Accelerometer, ppSymbolZ);



            X.ReadingChanged += new EventHandler<Axis.ReadingChangedEventArgs>(axis_ReadingChanged);
            Y.ReadingChanged += new EventHandler<Axis.ReadingChangedEventArgs>(axis_ReadingChanged);
            Z.ReadingChanged += new EventHandler<Axis.ReadingChangedEventArgs>(axis_ReadingChanged);

            Reset();
            Accelerometer.Start();
        }

        private void axis_ReadingChanged(object sender, Axis.ReadingChangedEventArgs e)
        {

            Axis.AxisDegreeInfo rawDegree = Axis.AxisDegreeInfo.ConvertToDegreeInfo(e.AxisGraph.AxisRaw);
            if (CurrentAxis != null)
            {
                CurrentAxis.AxisOffset = new Axis.AxisDegreeInfo(sX.Value, sY.Value, sZ.Value);

                txtXDegreeFinal.Text = ((Int32)Axis.AxisDegreeInfo.Wrap(CurrentAxis.Axis.X + CurrentAxis.AxisOffset.X)).ToString();
                txtYDegreeFinal.Text = ((Int32)Axis.AxisDegreeInfo.Wrap(CurrentAxis.Axis.Y + CurrentAxis.AxisOffset.Y)).ToString();
                txtZDegreeFinal.Text = ((Int32)Axis.AxisDegreeInfo.Wrap(CurrentAxis.Axis.Z + CurrentAxis.AxisOffset.Z)).ToString();

                txtX.Text = CurrentAxis.AxisRaw.X.ToString("0.00");
                txtY.Text = CurrentAxis.AxisRaw.Y.ToString("0.00");
                txtZ.Text = CurrentAxis.AxisRaw.Z.ToString("0.00");


                txtXDegree.Text = ((Int32)rawDegree.X).ToString();
                txtYDegree.Text = ((Int32)rawDegree.Y).ToString();
                txtZDegree.Text = ((Int32)rawDegree.Z).ToString();

                txtXDegreeOffset.Text = ((Int32)CurrentAxis.AxisOffset.X).ToString();
                txtYDegreeOffset.Text = ((Int32)CurrentAxis.AxisOffset.Y).ToString();
                txtZDegreeOffset.Text = ((Int32)CurrentAxis.AxisOffset.Z).ToString();
                
            }
            else
            {
                txtXRawDegree.Text = ((Int32)rawDegree.X).ToString();
                txtYRawDegree.Text = ((Int32)rawDegree.Y).ToString();
                txtZRawDegree.Text = ((Int32)rawDegree.Z).ToString();

                txtXRaw.Text = e.AxisGraph.AxisRaw.X.ToString("0.00");
                txtYRaw.Text = e.AxisGraph.AxisRaw.Y.ToString("0.00");
                txtZRaw.Text = e.AxisGraph.AxisRaw.Z.ToString("0.00");
            }
        }

        private void btnSimpleMode_Click(object sender, RoutedEventArgs e)
        {
            NavigationService.Navigate(new Uri("/SimplePage.xaml", UriKind.RelativeOrAbsolute));
        }

        private void cbxXVisible_Click(object sender, RoutedEventArgs e)
        {
            imgSymbolX.Visibility = (cbxXVisible.IsChecked.Value) ? Visibility.Visible : Visibility.Collapsed;
            ResetTab();
        }

        private void cbxYVisible_Click(object sender, RoutedEventArgs e)
        {
            imgSymbolY.Visibility = (cbxYVisible.IsChecked.Value) ? Visibility.Visible : Visibility.Collapsed;
            ResetTab();
        }

        private void cbxZVisible_Click(object sender, RoutedEventArgs e)
        {
            imgSymbolZ.Visibility = (cbxZVisible.IsChecked.Value) ? Visibility.Visible : Visibility.Collapsed;
            ResetTab();
        }

        private void btnDefault_Click(object sender, RoutedEventArgs e)
        {
            CurrentAxis = null;
            ResetTab();
        }

        private void btnX_Click(object sender, RoutedEventArgs e)
        {
            CurrentAxis = X;
            ResetTab();
        }
       
        private void btnY_Click(object sender, RoutedEventArgs e)
        {
            CurrentAxis = Y;
            ResetTab();
        }

        private void btnZ_Click(object sender, RoutedEventArgs e)
        {
            CurrentAxis = Z;
            ResetTab();
        }
      
        private void btnMappingX_Click(object sender, RoutedEventArgs e)
        {
            CurrentAxis.MappingX = Axis.AxisGraphBasicInfo.GetNextAxis(CurrentAxis.MappingX);
            ResetTab();
        }

        private void btnMappingY_Click(object sender, RoutedEventArgs e)
        {

            CurrentAxis.MappingY = Axis.AxisGraphBasicInfo.GetNextAxis(CurrentAxis.MappingY);
            ResetTab();
        }

        private void btnMappingZ_Click(object sender, RoutedEventArgs e)
        {
            CurrentAxis.MappingZ = Axis.AxisGraphBasicInfo.GetNextAxis(CurrentAxis.MappingZ);
            ResetTab();
        }

        private void ResetTab()
        {
            if (CurrentAxis == null)
            {
                lblVersion.Visibility = Visibility.Visible;
                grdDefault.Visibility = Visibility.Visible;


                grdControls.Visibility = Visibility.Collapsed;
                lblEditingX.Visibility = Visibility.Collapsed;
                lblEditingY.Visibility = Visibility.Collapsed;
                lblEditingZ.Visibility = Visibility.Collapsed;

                btnX.IsEnabled = (cbxXVisible.IsChecked.Value);
                btnY.IsEnabled = (cbxYVisible.IsChecked.Value);
                btnZ.IsEnabled = (cbxZVisible.IsChecked.Value);

                imgSymbolX.Visibility = (btnX.IsEnabled) ? Visibility.Visible : Visibility.Collapsed;
                imgSymbolY.Visibility = (btnY.IsEnabled) ? Visibility.Visible : Visibility.Collapsed;
                imgSymbolZ.Visibility = (btnZ.IsEnabled) ? Visibility.Visible : Visibility.Collapsed;

                btnX.Opacity = (btnX.IsEnabled) ? 0.5 : 1;
                btnY.Opacity = (btnY.IsEnabled) ? 0.5 : 1;
                btnZ.Opacity = (btnZ.IsEnabled) ? 0.5 : 1;

                btnDefault.BorderThickness = new Thickness(2);
                btnX.BorderThickness = new Thickness(1);
                btnY.BorderThickness = new Thickness(1);
                btnZ.BorderThickness = new Thickness(1);
            }
            else
            {
                lblVersion.Visibility = Visibility.Collapsed;
                grdDefault.Visibility = Visibility.Collapsed;

                grdControls.Visibility = Visibility.Visible;

                btnX.BorderThickness = new Thickness(((CurrentAxis == X) ? 2 : 1));
                btnY.BorderThickness = new Thickness(((CurrentAxis == Y) ? 2 : 1));
                btnZ.BorderThickness = new Thickness(((CurrentAxis == Z) ? 2 : 1));

                imgSymbolX.Visibility = (CurrentAxis == X) ? Visibility.Visible : Visibility.Collapsed;
                imgSymbolY.Visibility = (CurrentAxis == Y) ? Visibility.Visible : Visibility.Collapsed;
                imgSymbolZ.Visibility = (CurrentAxis == Z) ? Visibility.Visible : Visibility.Collapsed;

                grdControls.Visibility = Visibility.Visible;
                grdDefault.Visibility = Visibility.Collapsed;

                lblEditingX.Visibility = (CurrentAxis == X) ? Visibility.Visible : Visibility.Collapsed;
                lblEditingY.Visibility = (CurrentAxis == Y) ? Visibility.Visible : Visibility.Collapsed;
                lblEditingZ.Visibility = (CurrentAxis == Z) ? Visibility.Visible : Visibility.Collapsed;

                sX.Value = CurrentAxis.AxisOffset.X;
                sY.Value = CurrentAxis.AxisOffset.Y;
                sZ.Value = CurrentAxis.AxisOffset.Z;

                btnMappingX.Content = (CurrentAxis.MappingX.HasValue) ? String.Format("X = {0}", CurrentAxis.MappingX.Value) : "Off";
                btnMappingY.Content = (CurrentAxis.MappingY.HasValue) ? String.Format("Y = {0}", CurrentAxis.MappingY.Value) : "Off";
                btnMappingZ.Content = (CurrentAxis.MappingZ.HasValue) ? String.Format("Z = {0}", CurrentAxis.MappingZ.Value) : "Off";

                cbxInvertX.IsChecked = CurrentAxis.InverseX;
                cbxInvertY.IsChecked = CurrentAxis.InverseY;
                cbxInvertZ.IsChecked = CurrentAxis.InverseZ;
            }
        }

        private void Reset()
        {
            X.Reset(new Axis.AxisDegreeInfo(90, 0, 0));
            Y.Reset(new Axis.AxisDegreeInfo(0, 90, 0));
            Z.Reset(new Axis.AxisDegreeInfo(0, 0, 90));

            ResetTab();
        }

        public void Dispose()
        {
            X.Dispose();
            Y.Dispose();
            Z.Dispose();
        }

        private void cbxInvertX_Click(object sender, RoutedEventArgs e)
        {
            CurrentAxis.InverseX = cbxInvertX.IsChecked.Value;
            ResetTab();
        }

        private void cbxInvertY_Click(object sender, RoutedEventArgs e)
        {
            CurrentAxis.InverseY = cbxInvertY.IsChecked.Value;
            ResetTab();
        }

        private void cbxInvertZ_Click(object sender, RoutedEventArgs e)
        {
            CurrentAxis.InverseZ = cbxInvertZ.IsChecked.Value;
            ResetTab();
        }

        private void btnReset_Click(object sender, RoutedEventArgs e)
        {
            Reset();
        }

        private void btnCalabrate_Click(object sender, RoutedEventArgs e)
        {
            X.Calibrate(new Axis.AxisDegreeInfo(90, 0, 0));
            Y.Calibrate(new Axis.AxisDegreeInfo(0, 90, 0));
            Z.Calibrate(new Axis.AxisDegreeInfo(0, 0, 90));
            ResetTab();
        }

        private void ContentPanel_Loaded(object sender, RoutedEventArgs e)
        {
            SolidColorBrush backgroundBrush = Application.Current.Resources["PhoneBackgroundBrush"] as SolidColorBrush;

            if (backgroundBrush.Color == White)
            {
                imgXDegreeWhite.Visibility = Visibility.Visible;
                imgXDegree.Visibility = Visibility.Collapsed;
            }
            else
            {
                imgXDegreeWhite.Visibility = Visibility.Collapsed;
                imgXDegree.Visibility = Visibility.Visible;
            }
            btnReset.Background = backgroundBrush;
            btnCalabrate.Background = backgroundBrush;
        }
    }
}